<template>
  <div class="statistcsInfo">
    <courseHeadInfo :courseInfo="courseInfo" />
    <div class="statistcsInfo-content">
      <div class="tabsBox">
        <div class="tabsHead">
          <div
            class="title"
            :class="{ selectTab: selectTab == 'task' }"
            @click="selectTab = 'task'"
          >
            任务完成总况
          </div>
          <div
            class="title"
            :class="{ selectTab: selectTab == 'score' }"
            @click="selectTab = 'score'"
          >
            学生成绩总况
          </div>
          <div
            class="title"
            :class="{ selectTab: selectTab == 'taskScore' }"
            @click="selectTab = 'taskScore'"
          >
            任务成绩统计
          </div>
        </div>
        <div class="statisticalData">
          <task
            :taskCount="taskCount"
            :finshCount="finshCount"
            :studyCount="studyCount"
            :studentsList="studentsList"
            :taskOption="taskOption"
            :reviewOption="reviewOption"
            :studenData="studenData"
            :courseInfo="courseInfo"
            :tableLoading="tableLoading"
            :taskCountLoading="taskCountLoading"
            :taskIDforTaskGruopID="taskIDforTaskGruopID"
            v-show="selectTab == 'task'"
            @getStuData="getStuData"
          />
          <score
            :taskCount="taskCount"
            :finshCount="finshCount"
            :studyCount="studyCount"
            :studentsList="studentsList"
            :scoreOption="scoreOption"
            :reviewOption="reviewOption"
            :studenData="studenData"
            :scoreCount="scoreCount"
            :courseInfo="courseInfo"
            :tableLoading="tableLoading"
            :taskIDforTaskGruopID="taskIDforTaskGruopID"
            v-show="selectTab == 'score'"
            @getStuData="getStuData"
          />
          <taskScore
            :courseInfo="courseInfo"
            :studenData="studenData"
            :tableLoading="tableLoading"
            v-show="selectTab == 'taskScore'"
            @getStuTaskData="getStuTaskData"
          />
        </div>
      </div>
    </div>
  </div>
</template>

<script>
const courseHeadInfo = () =>
  import("@/components/teacherPage/courseHeadInfo/courseHeadInfo");
const task = () => import("./component/task");
const score = () => import("./component/score");
const taskScore = () => import("./component/taskScore");
import { handleChangeTaskCommitJsonToArray } from "@/util/courseData";
import { getCourseDetail, getCurriculumCourseInfo } from "@/request/courses";
import { formatCourseGroupTaskObj, formatTasks_Guideline } from "@/util/courseData";
import {
  getqueryreport,
  getalltaskdata,
  getCurrNoData,
  getMultistudydata,
  getChooseNoData
} from "@/request/teacher";
export default {
  components: {
    courseHeadInfo,
    task,
    score,
    taskScore,
  },
  data() {
    return {
      courseInfo: {},
      // 任务统计
      taskCount: [],
      // 学习人数
      studyCount: 0,
      // 总分
      scoreTotal: 100,
      // 完成人数统计
      finshCount: {
        finishedStuCount: [], // 完成
        studyingStuCount: [], // 在学
        notStartStuCount: [], // 未学
      },
      // 分数统计
      scoreCount: {
        maxScore: [], // 最高分
        avgScore: [], // 平均分
        minScore: [], // 最低分
      },
      courseData: {},
      selectTab: "task",
      studentsList: [], // 选修了这门课程的学生
      studenData: [], // 所有学生的学习数据
      taskOption: {
        finishCount: {
          name: "已学",
          value: 0,
          itemStyle: { normal: { color: "#91CD74" } },
          icon: "rect",
        },
        studyCount: {
          name: "在学",
          value: 0,
          itemStyle: { normal: { color: "#F9C957" } },
          icon: "rect",
        },
        notStartCount: {
          name: "未学",
          value: 0,
          itemStyle: { normal: { color: "#F56161" } },
          icon: "rect",
        },
      },
      reviewOption: {
        reviewedCount: {
          name: "已批",
          value: 0,
          itemStyle: { normal: { color: "#91CD74" } },
          icon: "rect",
        },
        reviewingCount: {
          name: "在批",
          value: 0,
          itemStyle: { normal: { color: "#F9C957" } },
          icon: "rect",
        },
        noReviewCount: {
          name: "未批",
          value: 0,
          itemStyle: { normal: { color: "#F56161" } },
          icon: "rect",
        },
      },
      scoreOption: {
        "100-90": {
          name: "100-90",
          value: 0,
          itemStyle: { normal: { color: "#73C0DE" } },
          icon: "rect",
          children: [],
        },
        "90-80": {
          name: "90-80",
          value: 0,
          itemStyle: { normal: { color: "#91CC75" } },
          icon: "rect",
          children: [],
        },
        "80-70": {
          name: "80-70",
          value: 0,
          itemStyle: { normal: { color: "#5470C6" } },
          icon: "rect",
          children: [],
        },
        "70-60": {
          name: "70-60",
          value: 0,
          itemStyle: { normal: { color: "#FAC858" } },
          icon: "rect",
          children: [],
        },
        "60-0": {
          name: "60-0",
          value: 0,
          itemStyle: { normal: { color: "#EE6666" } },
          icon: "rect",
          children: [],
        },
      },
      tableLoading: false, // 表格数据加载
      taskCountLoading: false, // 任务数据统计加载
      taskIDforTaskGruopID: {}, // 任务ID归属的任务组ID
    };
  },
  watch: {
    studentsList(n) {},
    finshCount(n) {
      const toKey = {
        finishedStuCount: "finishCount",
        studyingStuCount: "studyCount",
        notStartStuCount: "notStartCount",
      };
      Object.keys(n).forEach((item) => {
        this.taskOption[toKey[item]].value =
          (
            (n[item].reduce((prev, next) => {
              return (next < 0 ? 0 : next) + prev;
            }) /
              n[item].length) *
            100
          )?.toFixed(2) || 0;
      });
    },
    studenData(n) {
      const key = {
        reviewedCount: { key: "reviewedCount", value: 0 },
        reviewingCount: { key: "reviewingCount", value: 0 },
        noReviewCount: { key: "noReviewCount", value: 0 },
      };

      const scoreKey = {
        "100-90": { key: "100-90", value: 0 },
        "90-80": { key: "90-80", value: 0 },
        "80-70": { key: "80-70", value: 0 },
        "70-60": { key: "70-60", value: 0 },
        "60-0": { key: "60-0", value: 0 },
      };

      n.forEach((item) => {
        item.finishedTaskResultArray.forEach(fitem => {
          if (fitem.reviewState === "已批") {
            key["reviewedCount"].value++
          } else if (fitem.reviewState === "在批") {
            key["reviewingCount"].value++
          } else {
            key["noReviewCount"].value++
          }
        })
        // item.allTaskResultsInChooseNo.forEach((taskItem, t) => {
        //   let noReview = taskItem.guidelines.filter(
        //     (guideline) =>
        //       guideline.guidelineComment == "" &&
        //       (guideline.guidelineScore == -8 ||
        //         guideline.gameOrExciseScore == -8)
        //   );
        //   if (noReview.length == taskItem.guidelines.length) {
        //     key["noReviewCount"].value++;
        //     return;
        //   }
        //   let reviewing = taskItem.guidelines.filter(
        //     (guideline) =>
        //       guideline.guidelineComment !== "" &&
        //       (guideline.guidelineScore !== -8 ||
        //         guideline.gameOrExciseScore !== -8)
        //   );
        //   if (
        //     reviewing.length !== 0 &&
        //     reviewing.length == taskItem.guidelines.length
        //   ) {
        //     key["reviewedCount"].value++;
        //   } else {
        //     if (!taskItem.guidelines.length) return;
        //     key["reviewingCount"].value++;
        //   }
        // });

        Object.keys(this.scoreOption).forEach((sK) => {
          if (
            Number(sK.split("-")[0]) > Number(item.score) &&
            Number(item.score) >= Number(sK.split("-")[1])
          ) {
            this.scoreOption[sK].value++;
            if (
              !this.scoreOption[sK].children.find(
                (f) => f.userID === item.userID
              )
            ) {
              this.scoreOption[sK].children.push(item);
            }
          }
        });
      });

      let allTaskCount = 0;
      Object.keys(key).forEach((item) => {
        this.reviewOption[item].value = key[item].value;
        allTaskCount = allTaskCount + key[item].value;
      });
      Object.keys(this.reviewOption).forEach((item) => {
        const currItem = this.reviewOption[item];
        currItem.value =
          ((currItem.value / allTaskCount) * 100)?.toFixed(2) || 0;
      });
    },
  },
  async created() {
    const { query, params } = this.$route;
    if (!query.currNo) {
      if (!Number(params.id)) {
        return this.$antdMessage.error({
          content: "课程ID无效！",
        });
      } else {
        query.currNo = Number(params.id);
      }
    }
    this.tableLoading = true;
    this.taskCountLoading = true;
    // 获取任务的统计数据
    this.handelFetchLocalData();
    // 获取班级数据
    this.$store.dispatch("class/gClassList")
    // 获取选修了这门课程的学生
    const getAllStuID = await this.fetchCurrNoData({
      currNo: Number(query.currNo),
      className: query.filter
        ? query.filter.indexOf("全部") !== -1
          ? undefined
          : query.filter
        : undefined,
    });
    // const userIDArr = this.studentsList.map((item) => item.userID);
    // getAllStuID &&
    //   userIDArr.length &&
    //   this.fetchMultistudydata({
    //     currNo: Number(query.currNo),
    //     userIDArray: userIDArr,
    //   });
  },
  methods: {
    // 添加标签
    setTagsViewTitle(name) {
      if (this.$route.path === "/") return;
      const title = this.$route.meta.name;
      const courseName = name.name;
      const route = Object.assign({}, this.$route, {
        title: courseName ? courseName : ` ${title}-${this.$route.params.id}`,
      });
      this.$store.dispatch("tagsView/updateVisitedView", route);
    },
    // 获取课程详情
    async fetchCourseInfo(params) {
      return new Promise((resolve, reject) => {
        const courseInfo = getCourseDetail(params);
        const currCourseInfo = getCurriculumCourseInfo({
          id: this.$route.query.currNo,
        });
        Promise.all([courseInfo, currCourseInfo]).then((res) => {
          formatCourseGroupTaskObj(res[0].data, this);
          res[0].data.name = res[1].data.name;
          this.courseInfo = res[0].data;
          this.courseData = res[1].data;
          this.courseInfo.classIDList = this.courseData.classIDList
          const obj = {};
          res[0].data.content.forEach((item) => {
            item.tasks.forEach((titem) => {
              obj[titem.taskID] = item.taskGroupID;
            });
          });
          this.taskIDforTaskGruopID = obj;
          this.setTagsViewTitle({ name: this.courseInfo.name });
          resolve(res[0]);
        });
      });
    },
    // 统计所有学生的学习数据
    fetchTaskData(params) {
      return new Promise((resolve, reject) => {
        getalltaskdata(params).then((data) => {
          resolve({errno: 0, data: data});
        });
      });
    },
    // 获取学生学习数据
    // fetchMultistudydata(params) {
    //   this.tableLoading = true;
    //   getMultistudydata(params)
    //     .then((res) => {
    //       if (res.errno === 0) {
    //         res.data.forEach((item) => {
    //           item.taskCommitJson = Object.assign({}, item.taskGroupResults);
    //           item.taskCommitJson = handleChangeTaskCommitJsonToArray(
    //             item.taskCommitJson
    //           );
    //         });
    //         this.studenData = res.data;
    //       } else {
    //         this.$antdMessage.error({
    //           content: res.message,
    //         });
    //       }
    //       this.tableLoading = false;
    //     })
    //     .catch((err) => {
    //       this.tableLoading = false;
    //     });
    // },
    // 调取接口同步数据
    async handelFetchData(
      params = {
        currNo: Number(this.$route.query.currNo),
        className: this.$route.query.filter
          ? this.$route.query.filter.indexOf("全部") !== -1
            ? undefined
            : this.$route.query.filter
          : undefined,
      }
    ) {
      let courseInfo = await this.fetchCourseInfo({
        id: Number(this.$route.query.courseID),
      });
      let courseData = this.fetchTaskData(params);
      Promise.all([courseInfo, courseData])
        .then((res) => {
          let data = res[1].data;

          if (res[0].errno === 0 && res[1].errno === 0) {
            this.courseInfo = res[0].data;
            this.handleInitAllData();

            // 将任务组统计
            this.courseInfo.content.forEach((item) => {
              item.tasks.forEach((titem) => {
                this.taskCount.push({
                  value: titem.name,
                  taskGroupID: item.taskGroupID,
                  taskID: titem.taskID,
                });
              });
            });

            // 给任务初始化数据
            this.taskCount.forEach((item, index) => {
              // 遍历对象 将每一个key都遍历一遍 item.key为数组 将key的值设为
              Object.keys(this.finshCount).forEach((item) => {
                this.finshCount[item][index] = 0;
              });
              Object.keys(this.scoreCount).forEach((item) => {
                this.scoreCount[item][index] = 0;
              });
            });

            let countFinish = Object.assign({}, this.finshCount);
            let countScore = Object.assign({}, this.scoreCount);
            // 当课程没有数据时 重新赋默认值 触发图表的监听数据变化(watch)
            if (!data.length) {
              this.studyCount = 0;
              this.finshCount = Object.assign({}, this.finshCount);
              this.scoreCount = Object.assign({}, this.scoreCount);
              this.handelSaveData();
              return;
            }
            // 查找所有的任务数据
            this.taskCount.forEach((item, index) => {
              let findGourp = data.filter((ritem) => {
                return ritem.taskID === item.taskID;
              });
              // 将所有的任务数据 以任务的索引值为基准赋值给对应属性
              if (findGourp.length) {
                findGourp.forEach((fitem) => {
                  Object.keys(countFinish).forEach((oitem) => {
                    countFinish[oitem][index] = fitem[oitem];
                  });

                  Object.keys(countScore).forEach((oitem) => {
                    countScore[oitem][index] =
                      fitem[oitem] >= 0 ? fitem[oitem] : 0;
                    // if (fitem[oitem] != -8) {
                    // } else {
                    //   countScore[oitem][index] = null;
                    // }
                  });
                });
                this.finshCount = countFinish;
                this.scoreCount = countScore;
              }
            });
            this.studyCount =
              data[0].finishedStuCount +
              data[0].studyingStuCount +
              data[0].notStartStuCount;
            this.handelSaveData();
            this.taskCountLoading = false;
          }
        })
        .catch((err) => {
          this.taskCountLoading = false;
        });
    },
    // 获取本地数据
    async handelFetchLocalData() {
      // 获取当前时间
      let currTime = new Date().getTime();
      let tenMinute = 600000; // 10分钟
      // 获取本地数据
      // localStorage.setItem('echartsBarAllTaskCount', '[{"a":2}]')
      let getEchartsbarAllTaskCount = localStorage.getItem(
        "echartsBarAllTaskCount"
      );
      // 如果本地数据存在 转换JSON类型
      if (getEchartsbarAllTaskCount) {
        getEchartsbarAllTaskCount = JSON.parse(getEchartsbarAllTaskCount);
      } else {
        getEchartsbarAllTaskCount = [];
      }
      // 如果有数据在本地
      if (getEchartsbarAllTaskCount.length) {
        // 查找是否有匹配的数据
        let findEBCouDaAlTask = getEchartsbarAllTaskCount.filter((item) => {
          return item.currNo === Number(this.$route.query.currNo);
        });
        // 如果有匹配的数据
        if (findEBCouDaAlTask.length) {
          if (currTime - findEBCouDaAlTask[0].setTime < tenMinute) {
            // 等待课程信息返回
            await this.fetchCourseInfo({
              id: Number(this.$route.query.courseID),
            });
            this.$nextTick(() => {
              this.studyCount = findEBCouDaAlTask[0].studyCount;
              this.finshCount = findEBCouDaAlTask[0].finshCount;
              this.scoreCount = findEBCouDaAlTask[0].scoreCount;
              this.taskCount = findEBCouDaAlTask[0].taskCount;
            });
            this.taskCountLoading = false;
          } else {
            // 调取接口获取数据
            this.handelFetchData();
          }
        } else {
          // 调取接口获取数据
          this.handelFetchData();
        }
      } else {
        // 调取接口获取数据
        this.handelFetchData();
      }
    },
    // 将图表数据保存在本地
    handelSaveData() {
      // 获取本地数据
      let getEchartsbarAllTaskCount = localStorage.getItem(
        "echartsBarAllTaskCount"
      );
      // 如果本地数据存在 转换JSON类型
      if (getEchartsbarAllTaskCount) {
        getEchartsbarAllTaskCount = JSON.parse(getEchartsbarAllTaskCount);
      } else {
        getEchartsbarAllTaskCount = [];
      }
      // 如果有数据在本地
      if (getEchartsbarAllTaskCount.length) {
        // 查找是否有匹配的数据
        let findNotEBCouDaAlTask = getEchartsbarAllTaskCount.filter((item) => {
          return item.currNo !== Number(this.$route.query.currNo);
        });
        findNotEBCouDaAlTask.push({
          currNo: Number(this.$route.query.currNo),
          setTime: new Date().getTime(),
          studyCount: this.studyCount,
          taskCount: this.taskCount,
          finshCount: this.finshCount,
          scoreCount: this.scoreCount,
        });
        this.setLocalStorage(JSON.stringify(findNotEBCouDaAlTask));
      } else {
        this.setLocalStorage(
          JSON.stringify([
            {
              currNo: Number(this.$route.query.currNo),
              setTime: new Date().getTime(),
              studyCount: this.studyCount,
              taskCount: this.taskCount,
              finshCount: this.finshCount,
              scoreCount: this.scoreCount,
            },
          ])
        );
      }
    },
    // 设置数据
    setLocalStorage(str) {
      localStorage.setItem("echartsBarAllTaskCount", str);
    },
    // 初始化所有数据
    handleInitAllData() {
      this.taskCount = [];
      this.studyCount = 0;
      this.finshCount = {
        finishedStuCount: [], // 完成
        studyingStuCount: [], // 在学
        notStartStuCount: [], // 未学
      };
      this.scoreCount = {
        maxScore: [], // 最高分
        avgScore: [], // 平均分
        minScore: [], // 最低分
      };
    },
    // 获取对应课程学生的基本选修数据
    fetchCurrNoData(params) {
      return new Promise((resolve, reject) => {
        getCurrNoData(params)
          .then((data) => {
            if (data) {
              this.studentsList = data;
              this.handelSort("stuNum", true);
              data.forEach((item) => {
                // item.allTaskResultsInChooseNo.forEach((taskitem) => {
                //   taskitem.guidelines = Object.keys(
                //     taskitem.guidelineResults
                //   ).map((gitem) => taskitem.guidelineResults[gitem]);
                // });
              });
              this.studenData = data;
              resolve(true);
            } else {
              this.$antdMessage.error({
                content: "获取对应学生的选修数据失败!",
              });
              resolve(false);
            }
            this.tableLoading = false;
          })
          .catch((err) => {
            this.tableLoading = false;
          });
      });
    },
    // 排序 todo 有的时候顺序不一样
    handelSort(name, firstFormat) {
      if (this.sortName === name)
        return (this.sortName = ""), this.handelSort("stuNum", true);
      if (name === "realName") {
        this.studentsList.sort(function (a, b) {
          return a[name]?.localeCompare(b[name]);
        });
      } else if (name == "finishedCount") {
        this.studentsList
          .sort(function (a, b) {
            return (
              a[name] - b[name] ||
              a["studyingCount"] - b["studyingCount"] ||
              !(a["notStartCount"] - b["notStartCount"])
            );
          })
          .reverse();
      } else {
        this.studentsList.sort((a, b) => {
          return a[name] - b[name];
        });
      }
      // debugger
      if (!firstFormat) this.sortName = name;
    },
    // 获取某个学生的学习数据
    async getStuData(userID, fn, {row, isTask, that}) {
      const findUser = this.studentsList.find(item => item.userID == userID)
      if (!findUser) return
      if (!findUser.allTaskResultsInChooseNo || findUser.isGetOnlyTask) {
        const { query } = this.$route
        const res = await getChooseNoData({chooseNo: row.chooseNo, currNo: query.currNo})
        if (res.errno !== 0) return this.$antdMessage.error({content: res.message || "获取学生学习数据失败!"})
        if (res.errno === 0) {
          const taskGroup = Object.values(res.data.taskGroupResults)
          const tasks = taskGroup.map(item => Object.values(item.taskResults)).flat()
          formatTasks_Guideline(tasks)
          this.$set(findUser, "allTaskResultsInChooseNo", tasks)
          this.$set(findUser, "getAllTask", true)
          this.$set(findUser, "isGetOnlyTask", false)
        }
      } else return findUser.allTaskResultsInChooseNo
      fn(row, isTask, that)
    },
    // 根据学生ID列表获取某个任务的学习数据
    async getStuTaskData(params, fn, that) {
      const data = await getMultistudydata(params)
      if (!data) return this.$antdMessage.error({content: "获取学生任务数据失败!"})
      data.forEach(item => {
        const findUser = this.studentsList.find(fitem => fitem.chooseNo == item.chooseNo)
        if (findUser) {
          formatTasks_Guideline([item])
          if (findUser.allTaskResultsInChooseNo) {
            // 判断任务是否存在
            let getTask = findUser.allTaskResultsInChooseNo.find(sitem => sitem.taskID == item.taskID)
            if (getTask) {
              getTask = item
            } else {
              findUser.allTaskResultsInChooseNo.push(item)
            }
          } else {
            this.$set(findUser, "allTaskResultsInChooseNo", [item])
            this.$set(findUser, "isGetOnlyTask", true)
          }
        }
      })
      // 回调
      fn(that)
    }
  },
};
</script>

<style lang="stylus">
.statistcsInfo {
  .statistcsInfo-content {
    margin-top: 10px;
    padding-bottom: 10px;

    .tabsBox {
      margin: 0 auto;
      width: 1200px;
      height: 900px;
      background-color: #e7e7e7;
      border-radius: 10px 10px 10px 10px;

      .tabsHead {
        height: 60px;
        display: flex;
        justify-content: space-between;
        align-items: center;
        background: #fff;

        .title {
          cursor: pointer;
          flex: 1;
          font-family: SimHei;
          font-size: 2rem;
          color: #1e1c1c;
          text-align: center;
          line-height: 60px;
        }

        .selectTab {
          position: relative;
          color: #025183;
        }

        .selectTab::after {
          position: absolute;
          content: '';
          height: 3px;
          width: 100%;
          background: #025183;
          bottom: 0;
          left: 0;
        }
      }

      .statisticalData {
        padding: 12px 20px 20px 20px;
      }
    }
  }
}
</style>